/*******************************************************************/
/* @ All Rights Reserved Copyright (C) 2014 broada,Co.,Ltd.        */
/*                                                                 */
/*  NAME      = wtc_tcm.c                                          */
/*  NOTE      =                                                    */
/*  DATE      = 2015/08/26 by songbb                               */
/*******************************************************************/

#include "frreport_comm.h"

#include "wtc_core.h"
#include "wtc_comm.h"
#include "wtc_mar.h"
#include "wtc_tch.h"
#include "wtc_tcm.h"
#include "tcb/wtc_tcb_user.h"
#include "tcb/wtc_tcb_meta.h"
#include "tcb/wtc_tcb_tdom.h"
#include "tcb/wtc_tcb_tdomtran.h"
#include "tcb/wtc_tcb_tran.h"
#include "tcb/wtc_tcb_ws.h"
#include "tcb/wtc_tcb_unsol.h"
#include "tcb/wtc_tcb_composhdr.h"
#include "tcb/wtc_tcb_composfml.h"
#include "tcb/wtc_tcb_route.h"
#include "tcb/wtc_tcb_aaa.h"
#include "tcb/wtc_tcb_callout.h"
#include "tcb/wtc_tcb_tdomvals.h"
#include "tcb/wtc_tcb_codeset.h"

int wtc_read_tcm_by_idx(Conntrack *p_st_conn
                        , Apm_packet *p_analyze_in
                        , L7session_wtc *p_st_sess
                        , L7_wtc_packet *p_st_wtc_packet
                        , int i_hint_index
                        , Frreport_body_data **pp_st_body)
{
    WTC_PRINT_INFO("wtc_read_tcm_by_idx...\n");
    int i_read_bytes = 0;
    int i_recv_size = 0;
    int i_pos = 0;
    WTC_tch_header st_tch_header;
    memset(&st_tch_header, 0x00, sizeof(WTC_tch_header));

    i_pos = bytebuff_getPosition(p_st_wtc_packet->p_st_packet);

    if (wtc_read_tch(p_st_wtc_packet, &st_tch_header) != FR_SUCC)
        goto error;

    i_read_bytes = wtc_mar_roundup4(st_tch_header.len);
    i_recv_size = st_tch_header.len - APM_WTC_TCH_SIZE;

    if (wtc_tcb_user_tmpostrecv(p_st_conn, p_analyze_in, p_st_sess, p_st_wtc_packet, i_recv_size, i_hint_index, pp_st_body) != FR_SUCC)
        goto error;

    if (bytebuff_setPosition(p_st_wtc_packet->p_st_packet, i_pos + i_read_bytes) != FR_SUCC)
        goto error;

    return FR_SUCC;
error:
    return FR_FAIL;
}

int wtc_read_tcm_by_hdr(Conntrack *p_st_conn
                        , Apm_packet *p_analyze_in
                        , L7session_wtc *p_st_sess
                        , L7_wtc_packet *p_st_wtc_packet
                        , WTC_tch_header st_tch_header)
{
    WTC_PRINT_INFO("wtc_read_tcm_by_hdr... tcb_type:[%s]\n", WTC_TCBTYPE2STR(st_tch_header.tcb_type));
    int i_recv_size = st_tch_header.len - APM_WTC_TCH_SIZE;

    switch (st_tch_header.tcb_type)
    {
        case APM_WTC_TCB_TRAN:          // 2
            if (wtc_tcb_tran_tmpostrecv(p_st_conn, p_analyze_in, p_st_sess, p_st_wtc_packet, i_recv_size, -1) != FR_SUCC)
                goto error;
            break;
        case APM_WTC_TCB_WS:            // 3
            if (wtc_tcb_ws_tmpostrecv(p_st_conn, p_analyze_in, p_st_sess, p_st_wtc_packet, i_recv_size, -1) != FR_SUCC)
                goto error;
            break;
        case APM_WTC_TCB_UNSOL:         // 4
            if (wtc_tcb_unsol_tmpostrecv(p_st_conn, p_analyze_in, p_st_sess, p_st_wtc_packet, i_recv_size, -1) != FR_SUCC)
                goto error;
            break;
        case APM_WTC_TCB_COMPOS_HDR:    // 5
            if (wtc_tcb_composhdr_tmpostrecv(p_st_conn, p_analyze_in, p_st_sess, p_st_wtc_packet, i_recv_size, -1) != FR_SUCC)
                goto error;
            break;
        case APM_WTC_TCB_COMPOS_FML:    // 6
            if (wtc_tcb_composfml_tmpostrecv(p_st_conn, p_analyze_in, p_st_sess, p_st_wtc_packet, i_recv_size, -1) != FR_SUCC)
                goto error;
            break;
        case APM_WTC_TCB_TDOM:          // 7
            if (wtc_tcb_tdom_tmpostrecv(p_st_conn, p_analyze_in, p_st_sess, p_st_wtc_packet, i_recv_size, -1) != FR_SUCC)
                goto error;
            break;
        case APM_WTC_TCB_ROUTE:         // 9
            if (wtc_tcb_route_tmpostrecv(p_st_conn, p_analyze_in, p_st_sess, p_st_wtc_packet, i_recv_size, -1) != FR_SUCC)
                goto error;
            break;
        case APM_WTC_TCB_TDOM_TRAN:     // 10
            if (wtc_tcb_tdomtran_tmpostrecv(p_st_conn, p_analyze_in, p_st_sess, p_st_wtc_packet, i_recv_size, -1) != FR_SUCC)
                goto error;
            break;
        case APM_WTC_TCB_AAA_TCM:       // 15
            if (wtc_tcb_aaa_tmpostrecv(p_st_conn, p_analyze_in, p_st_sess, p_st_wtc_packet, i_recv_size, -1) != FR_SUCC)
                goto error;
            break;
        case APM_WTC_TCB_CALLOUT:       // 16
            if (wtc_tcb_callout_tmpostrecv(p_st_conn, p_analyze_in, p_st_sess, p_st_wtc_packet, i_recv_size, -1) != FR_SUCC)
                goto error;
            break;
        case APM_WTC_TCB_TDOM_VALS:     // 17
            if (wtc_tcb_tdomvals_tmpostrecv(p_st_conn, p_analyze_in, p_st_sess, p_st_wtc_packet, i_recv_size, -1) != FR_SUCC)
                goto error;
            break;
        case APM_WTC_TCB_CODESET_TCM:   // 18
            if (wtc_tcb_codeset_tmpostrecv(p_st_conn, p_analyze_in, p_st_sess, p_st_wtc_packet, i_recv_size, -1) != FR_SUCC)
                goto error;
            break;
        case APM_WTC_TCB_META_TCM:      // 19
            if (wtc_tcb_meta_tmpostrecv(p_st_conn, p_analyze_in, p_st_sess, p_st_wtc_packet, i_recv_size, -1) != FR_SUCC)
                goto error;
            break;
        case APM_WTC_TCB_TDOM_SEC:      // 8
        case APM_WTC_TCB_TEST_TCM:      // 11
        case APM_WTC_TCB_PKCS7_TCM:     // 12
        case APM_WTC_TCB_QS_TCM:        // 13
        case APM_WTC_TCB_PROP_TCM:      // 14
        default:
            if (bytebuff_skip(p_st_wtc_packet->p_st_packet, (size_t) i_recv_size) != FR_SUCC)
                goto error;
            break;
    }

    return FR_SUCC;
error:
    return FR_FAIL;
}


//////////////////////// for analyze direction
int wtc_read_tcm_by_idx_fad(int i_hint_index
                            , char *p_payload
                            , unsigned int ui_payload_len
                            , unsigned int *p_ui_offset)
{
    WTC_PRINT_INFO("wtc_read_tcm_by_idx_fad...\n");
    int i_read_bytes = 0;
    int i_recv_size = 0;
    int i_pos = 0;
    WTC_tch_header st_tch_header;
    memset(&st_tch_header, 0x00, sizeof(WTC_tch_header));

    i_pos = *p_ui_offset;

    if (wtc_read_tch_fad(p_payload, ui_payload_len, p_ui_offset, &st_tch_header) != FR_SUCC)
        goto error;

    i_read_bytes = wtc_mar_roundup4(st_tch_header.len);
    i_recv_size = st_tch_header.len - APM_WTC_TCH_SIZE;

    if (wtc_tcb_user_tmpostrecv_fad(i_recv_size, i_hint_index, p_payload, ui_payload_len, p_ui_offset) != FR_SUCC)
        goto error;

    *p_ui_offset = (unsigned int) (i_pos + i_read_bytes);

    if (*p_ui_offset > ui_payload_len)
        goto error;

    return FR_SUCC;
error:
    return FR_FAIL;
}

int wtc_read_tcm_by_hdr_fad(char *p_payload
                            , unsigned int ui_payload_len
                            , unsigned int *p_ui_offset
                            , WTC_tch_header st_tch_header
                            , int *p_i_direction)
{
    WTC_PRINT_INFO("wtc_read_tcm_by_hdr_fad... tcb_type:[%s]\n", WTC_TCBTYPE2STR(st_tch_header.tcb_type));
    int i_recv_size = st_tch_header.len - APM_WTC_TCH_SIZE;

    switch (st_tch_header.tcb_type)
    {
        case APM_WTC_TCB_TRAN:          // 2
            if (wtc_tcb_tran_tmpostrecv_fad(p_payload, ui_payload_len, p_ui_offset, p_i_direction, i_recv_size, -1) != FR_SUCC)
                goto error;
            break;
        case APM_WTC_TCB_WS:            // 3
            if (wtc_tcb_ws_tmpostrecv_fad(p_payload, ui_payload_len, p_ui_offset, p_i_direction, i_recv_size, -1) != FR_SUCC)
                goto error;
            break;
        case APM_WTC_TCB_UNSOL:         // 4
            if (wtc_tcb_unsol_tmpostrecv_fad(p_payload, ui_payload_len, p_ui_offset, p_i_direction, i_recv_size, -1) != FR_SUCC)
                goto error;
            break;
        case APM_WTC_TCB_COMPOS_HDR:    // 5
            if (wtc_tcb_composhdr_tmpostrecv_fad(p_payload, ui_payload_len, p_ui_offset, p_i_direction, i_recv_size, -1) != FR_SUCC)
                goto error;
            break;
        case APM_WTC_TCB_COMPOS_FML:    // 6
            if (wtc_tcb_composfml_tmpostrecv_fad(p_payload, ui_payload_len, p_ui_offset, p_i_direction, i_recv_size, -1) != FR_SUCC)
                goto error;
            break;
        case APM_WTC_TCB_TDOM:          // 7
            if (wtc_tcb_tdom_tmpostrecv_fad(p_payload, ui_payload_len, p_ui_offset, p_i_direction, i_recv_size, -1) != FR_SUCC)
                goto error;
            break;
        case APM_WTC_TCB_ROUTE:         // 9
            if (wtc_tcb_route_tmpostrecv_fad(p_payload, ui_payload_len, p_ui_offset, p_i_direction, i_recv_size, -1) != FR_SUCC)
                goto error;
            break;
        case APM_WTC_TCB_TDOM_TRAN:     // 10
            if (wtc_tcb_tdomtran_tmpostrecv_fad(p_payload, ui_payload_len, p_ui_offset, p_i_direction, i_recv_size, -1) != FR_SUCC)
                goto error;
            break;
        case APM_WTC_TCB_AAA_TCM:       // 15
            if (wtc_tcb_aaa_tmpostrecv_fad(p_payload, ui_payload_len, p_ui_offset, p_i_direction, i_recv_size, -1) != FR_SUCC)
                goto error;
            break;
        case APM_WTC_TCB_CALLOUT:       // 16
            if (wtc_tcb_callout_tmpostrecv_fad(p_payload, ui_payload_len, p_ui_offset, p_i_direction, i_recv_size, -1) != FR_SUCC)
                goto error;
            break;
        case APM_WTC_TCB_TDOM_VALS:     // 17
            if (wtc_tcb_tdomvals_tmpostrecv_fad(p_payload, ui_payload_len, p_ui_offset, p_i_direction, i_recv_size, -1) != FR_SUCC)
                goto error;
            break;
        case APM_WTC_TCB_CODESET_TCM:   // 18
            if (wtc_tcb_codeset_tmpostrecv_fad(p_payload, ui_payload_len, p_ui_offset, p_i_direction, i_recv_size, -1) != FR_SUCC)
                goto error;
            break;
        case APM_WTC_TCB_META_TCM:      // 19
            if (wtc_tcb_meta_tmpostrecv_fad(p_payload, ui_payload_len, p_ui_offset, p_i_direction, i_recv_size, -1) != FR_SUCC)
                goto error;
            break;
        case APM_WTC_TCB_TDOM_SEC:      // 8
        case APM_WTC_TCB_TEST_TCM:      // 11
        case APM_WTC_TCB_PKCS7_TCM:     // 12
        case APM_WTC_TCB_QS_TCM:        // 13
        case APM_WTC_TCB_PROP_TCM:      // 14
        default:
            if (wtc_skip(p_payload, ui_payload_len, p_ui_offset, i_recv_size) != FR_SUCC)
                goto error;
            break;
    }

    return FR_SUCC;
error:
    return FR_FAIL;
}
